#pragma once
#pragma once

#include "Precompiled.hpp"

template <class TemplatedClass>
class Factory : public FactoryInterface
{
public:
  Factory();
  virtual ~Factory();
  virtual void Delete(TypelessHandle* target);
  virtual bool IsValid(const TypelessHandle* target) const;
  virtual void* GetData(TypelessHandle* target);
  virtual const void* GetData(const TypelessHandle* target) const;
  unsigned int Size() const;
  void Clear();
  TemplatedClass& operator [] (unsigned int location);
  const TemplatedClass& operator [] (unsigned int location) const;
  Handle<TemplatedClass> GetHandleFromLocation(unsigned int location);
  const Handle<TemplatedClass> GetHandleFromLocation(unsigned int location) const;
  Handle<TemplatedClass> CreateNewObject();
private:
  unsigned int ConvertIndexToLocation(unsigned int index) const;
  unsigned int ConvertLocationToIndex(unsigned int location) const;
  unsigned int ConvertHandleToLocation(const TypelessHandle* target) const;
  void SwapElements(unsigned int location1, unsigned int location2);
  void SwapElementWithEnd(unsigned int location);
  void DeleteElement(unsigned int location);
  void DeleteEnd();
  std::vector<TemplatedClass> data;
  std::vector<unsigned int> IDVector;
  std::vector<unsigned int> indexToLocationVector;
  std::vector<unsigned int> locationToIndexVector;
  std::vector<unsigned int> availableIndeces;
  unsigned int currentID;
};

#include "Factory.cpp"